[BLK] front: Flush workqueues with no locks held. Operation can sleep.
authorkfraser@localhost.localdomain <kfraser@localhost.localdomain>
Fri, 29 Sep 2006 08:23:18 +0000 (09:23 +0100)
committerkfraser@localhost.localdomain <kfraser@localhost.localdomain>
Fri, 29 Sep 2006 08:23:18 +0000 (09:23 +0100)
Signed-off-by: Keir Fraser <keir@xensource.com>
linux-2.6-xen-sparse/drivers/xen/blkfront/blkfront.c

index 83630ee2ec8bfcae0a114b5f665a95c8586af2fd..e79b653a973fc9ec2a0a2e8ae4f7e8f4b65bbdf7 100644 (file)
@@ -355,9 +355,11 @@ static void blkfront_closing(struct xenbus_device *dev)
        blk_stop_queue(info->rq);
        /* No more gnttab callback work. */
        gnttab_cancel_free_callback(&info->callback);
-       flush_scheduled_work();
        spin_unlock_irqrestore(&blkif_io_lock, flags);
 
+       /* Flush gnttab callback work. Must be done with no locks held. */
+       flush_scheduled_work();
+
        xlvbd_del(info);
 
        xenbus_frontend_closed(dev);
@@ -714,9 +716,11 @@ static void blkif_free(struct blkfront_info *info, int suspend)
                blk_stop_queue(info->rq);
        /* No more gnttab callback work. */
        gnttab_cancel_free_callback(&info->callback);
-       flush_scheduled_work();
        spin_unlock_irq(&blkif_io_lock);
 
+       /* Flush gnttab callback work. Must be done with no locks held. */
+       flush_scheduled_work();
+
        /* Free resources associated with old device channel. */
        if (info->ring_ref != GRANT_INVALID_REF) {
                gnttab_end_foreign_access(info->ring_ref, 0,